// 检查数独解决方案
function checkArray(array) {
  const length = array.length
  const marks = new Array(length)
  marks.fill(true)

  for (let i = 0; i < 9; i++) {
    if (!marks[i]) continue

    const v = array[i]
    // 检查是否有效， 0 - 无效 1-9 有效
    if (!v) {
      marks[i] = false
      continue
    }

    // 是否有重复： i+1 ~ 9，是否与 i 位置的数据重复
    for (let j = i + 1; j < length; j++) {
      if (v === array[j]) {
        marks[i] = marks[j] = false
      }
    }
  }

  return marks
}

/**
 *  输入: matrix 9x9数独矩阵数据
 *  处理：对matrix 行、列、宫进行检查，并填写marks
 * 输出：检查是否成功，marks
*/
const Toolkit = require('./toolkit')

class Checker {
  constructor(matrix) {
    this._matrix = matrix
    this._matrixMarks= Toolkit.matrix.makeMatrix(true)
  }

  get MatrixMarks() {
    return this._matrixMarks
  }

  get isSuccess() {
    return this._success
  }

  check() {
    this.checkRows()
    this.checkCols()
    this.checkBoxes()

    // 检查是否成功
    return this._matrixMarks.every(row => row.every(mark => mark))
  }

  checkRows() {
    for (let rowIndex = 0; rowIndex < 9; rowIndex++) {
      const row = this._matrix[rowIndex]
      const marks = checkArray(row)

      for (let colIndex = 0; colIndex < 9; colIndex++) {
        if (!marks[colIndex]) {
          this._matrixMarks[rowIndex][colIndex] = false
        }
      }
    }
  }

  checkCols() {
    for (let colIndex = 0; colIndex < 9; colIndex++) {
      const cols = []
      for (let rowIndex = 0; rowIndex < 9; rowIndex++) {
        cols[rowIndex] = this._matrix[rowIndex][colIndex]
      }

      const marks = checkArray(cols)
      for (let rowIndex = 0; rowIndex < 9; rowIndex++) {
        if (!marks[rowIndex]) {
          this._matrixMarks[rowIndex][colIndex] = false
        }
      }
    }
  }

  checkBoxes() {
    for (let boxIndex = 0; boxIndex < 9; boxIndex++) {
      const boxes = Toolkit.box.getBoxCells(this._matrix, boxIndex)
      const marks = checkArray(boxes)

      for (let cellIndex = 0; cellIndex < 9; cellIndex++) {
        if (!marks[cellIndex]) {
          const {rowIndex, colIndex} = Toolkit.box.convertFromBoxIndex(boxIndex, cellIndex)
          this._matrixMarks[rowIndex][colIndex] = false
        }
      }
    }
  }
}

const Genarator = require('./generator')
const gen = new Genarator()

gen.generator()
const matrix = gen.matrix

const checker = new Checker(matrix)
console.log('checker.check() ====', checker.check())
console.log('matrixMakers', checker.MatrixMarks)

matrix[1][2] = 0
matrix[2][2] = matrix[3][3] = 5

const checker2 = new Checker(matrix)
console.log('checker2.check() ====', checker2.check())
console.log('matrixMakers2', checker2.MatrixMarks)
